from __main__ import *
import os
import subprocess
import logging
from utils import find_files


class OpenCSD:
    def __init__(self, openCSDPath: str, tracePath: str, traceID: int):
        logging.info(f"Running {__class__}")
        self.__traceID = traceID
        # find trc_pkt_lister
        self.__etmParser = find_files(openCSDPath, "trc_pkt_lister")
        if self.__etmParser is None:
            logging.error(f"The OpenCSD {openCSDPath} is invalid")
            raise FileNotFoundError("trc_pkt_lister")
        logging.debug("Found fromelf command. Path is: " + self.__etmParser)

        self.__libPath = find_files(openCSDPath, "libopencsd.so")
        if self.__libPath is None:
            logging.error(f"The OpenCSD is {openCSDPath} is invalid")
            raise FileNotFoundError("libopencsd.so")

        # check trace file exists
        if not os.path.exists(tracePath):
            logging.error("Unable to locate ELF file. Please check filepath entered.")
            raise FileNotFoundError(tracePath)
        self.__trace = tracePath
        self.__traceOutput = os.path.splitext(tracePath)[0] + "/decode.ppl"
        logging.debug("Found ELF file. Path is: " + self.__trace)

        self.__decode()

    def __decode(self):
        if os.path.exists(self.__traceOutput):
            logging.info("Trace is already decode. Skipping.")
            return

        # setting environment variable and running trc_pkt_lister command
        command = f'"{self.__etmParser}" -ss_dir "{self.__trace}" -decode -id {hex(self.__traceID)} -logfilename "{self.__traceOutput}"'
        env = {"LD_LIBRARY_PATH": os.path.dirname(self.__libPath)}
        logging.debug(f"env: {env}")
        logging.debug(f"executing command: {command}")
        # Actually run the fromelf command
        try:
            trace_decode = subprocess.check_output(
                command, shell=True, universal_newlines=True, env=env
            )
        except subprocess.CalledProcessError as e:
            logging.error(
                f"Failed to run the execute command: {command}. Please check {self.__traceOutput} for more detail."
            )
            raise e

        logging.info(
            "SUCCESSFULLY produced trace decode file using trc_pkt_lister tool"
        )

    def getTrace(self):
        return self.__traceOutput

